package nio.buffer;

import org.junit.Test;

import java.io.BufferedReader;
import java.nio.ByteBuffer;

/**
 * @author charwayH
 * 目标:对缓冲区Buffer的常用API进行案例实现
 * <p>
 * Buffer clear() 清空缓冲区并返回缓冲区的引用
 * Buffer flip()  将缓冲区的界限设置为当前位置，并将当前位置重置为0
 * int capacity()  返回Buffer的capacity大小
 * int limit()    返回Buffer的界限(limit)的位置
 * Buffer limit(int n)  将设置缓冲区界限为n，并返回一个具有新limit的缓冲区对象
 * Buffer mark()  对缓冲区设置标记位置
 * int position()  返回缓冲区的当前位置position
 * Buffer position(int n) 将设置缓冲区的当前位置为n，并返回修改后的Buffer对象
 * int remaining()   返回position和limit之间的元素个数
 * Buffer reset()   将位置position转到以前位置的mark所在的位置
 * Buffer rewind()   将位置设置为0，取消设置的mark
 */
public class BufferTest {
    String name = "charwayh";

    @Test
    @SuppressWarnings("all")
    public void test01() {
        System.out.println("1.-------------------------------");
        ByteBuffer buffer = ByteBuffer.allocate(10);
        // 1.分配一个缓冲区，容量设置为10
        System.out.println(buffer.position()); // 0
        System.out.println(buffer.limit()); // 10
        System.out.println(buffer.capacity()); // 10

        System.out.println("2.-------------------------------");

        // 2.put往缓冲区中添加数据
        buffer.put(name.getBytes());
        // 添加了8个字节
        System.out.println(buffer.position()); // 8
        System.out.println(buffer.limit()); // 10
        System.out.println(buffer.capacity()); // 10

        System.out.println("3.-------------------------------");

        // 3.Buffer.flip() 将缓冲区的界限设置为当前位置，并将当前位置值设为0   (可读模式)
        buffer.flip();
        System.out.println(buffer.position()); // 0
        System.out.println(buffer.limit()); // 8  （前8个字节位置可以读，后面的不可读）
        System.out.println(buffer.capacity()); // 10

        System.out.println("4.-------------------------------");

        // 4.get数据的获取
        char c = (char) buffer.get();
        System.out.println(c);
        System.out.println(buffer.position()); // 1
        System.out.println(buffer.limit()); // 8  （前8个字节位置可以读，后面的不可读）
        System.out.println(buffer.capacity()); // 10

    }

    @Test
    @SuppressWarnings("all")
    public void test02() {
        System.out.println("1.-------------------------------");
        // 1.分配一个缓冲区，容量设置成10，并添加内容
        ByteBuffer buffer = ByteBuffer.allocate(10);
        System.out.println(buffer.position()); // 0
        System.out.println(buffer.limit());    // 10
        System.out.println(buffer.capacity()); // 10
        buffer.put(name.getBytes());
        // clear缓冲区中的数据，并不是真正的清除了数据，而是把position变为了0
        System.out.println("clear缓冲区中的数据");
        buffer.clear();
        System.out.println(buffer.position()); // 0
        System.out.println(buffer.limit());    // 10
        System.out.println(buffer.capacity()); // 10
        System.out.println((char) buffer.get());

        System.out.println("2.-------------------------------");
        // 2.分配一个缓冲区，容量设置成10，并添加内容
        ByteBuffer buffer1 = ByteBuffer.allocate(10);
        buffer1.put(name.getBytes());
        buffer1.flip();

        // 读取数据
        byte[] b = new byte[2];
        buffer1.get(b);
        String rs = new String(b);
        System.out.println(rs);
        System.out.println(buffer1.position()); // 2
        System.out.println(buffer1.limit());    // 8
        System.out.println(buffer1.capacity()); // 10

        System.out.println("3.-------------------------------");
        // 标记此刻这个位置
        buffer1.mark();
        byte[] b2 = new byte[3];
        buffer1.get(b2);
        System.out.println(new String(b2));
        System.out.println(buffer1.position()); // 5
        System.out.println(buffer1.limit());    // 8
        System.out.println(buffer1.capacity()); // 10
        System.out.println("4.-------------------------------");
        // 回到标记位置
        buffer1.reset();
        // 是否还有未读字节
        if (buffer1.hasRemaining()) {
            // 剩余的未读字节
            System.out.println(buffer1.remaining());
        }
    }

    @Test
    @SuppressWarnings("all")
    public void test03() {
        // 1.创建一个直接内存的缓冲区
        ByteBuffer buffer = ByteBuffer.allocateDirect(1024);
        System.out.println(buffer.isDirect());
        ByteBuffer buffer1 = ByteBuffer.allocate(1024);
        System.out.println(buffer1.isDirect());
    }
}
